//------------------------------------------------------------------------------
// The contents of this file are subject to the nopCommerce Public License Version 1.0 ("License"); you may not use this file except in compliance with the License.
// You may obtain a copy of the License at  http://www.nopCommerce.com/License.aspx. 
// 
// Software distributed under the License is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. 
// See the License for the specific language governing rights and limitations under the License.
// 
// The Original Code is nopCommerce.
// The Initial Developer of the Original Code is NopSolutions.
// All Rights Reserved.
// 
// Contributor(s): _______. 
//------------------------------------------------------------------------------

using System;
using System.Collections.Generic;
using System.Data;
using System.Data.Common;
using System.Drawing;
using System.Drawing.Imaging;
using System.Globalization;
using System.IO;
using System.Text;
using System.Web;
using Microsoft.Practices.EnterpriseLibrary.Data;
using Tathata.Common.BLL.Entities;
using Tathata.Common.BLL.EntityCollections;
using Tathata.Common.Caching;
using Tathata.Common.DAL;
using Tathata.Common.DAL.Managers;
using Tathata.Common.Utils;

namespace Tathata.Common.BLL.Managers
{
    /// <summary>
    /// Picture manager
    /// </summary>
    public class PictureManager
    {
        #region Methods
        /// <summary>
        /// Get a picture URL
        /// </summary>
        /// <param name="imageId">Picture identifier</param>
        /// <returns>Picture URL</returns>
        public static string GetPictureUrl(int imageId)
        {
            Picture picture = GetByPictureID(imageId);
            return GetPictureUrl(picture);
        }

        /// <summary>
        /// Get a picture URL
        /// </summary>
        /// <param name="picture">Picture instance</param>
        /// <returns>Picture URL</returns>
        public static string GetPictureUrl(Picture picture)
        {
            return GetPictureUrl(picture, 0, 0);
        }

        /// <summary>
        /// Get a picture URL
        /// </summary>
        /// <param name="imageId">Picture identifier</param>
        /// <param name="Width">Width</param>
        /// <param name="Height">Height</param>
        /// <returns>Picture URL</returns>
        public static string GetPictureUrl(int imageId, int Width, int Height)
        {
            Picture picture = GetByPictureID(imageId);
            return GetPictureUrl(picture, Width, Height);
        }

        /// <summary>
        /// Get a picture URL
        /// </summary>
        /// <param name="picture">Picture instance</param>
        /// <param name="Width">Width</param>
        /// <param name="Height">Height</param>
        /// <returns>Picture URL</returns>
        public static string GetPictureUrl(Picture picture, int Width, int Height)
        {
            return GetPictureUrl(picture, Width, Height, true);
        }

        /// <summary>
        /// Get a picture URL
        /// </summary>
        /// <param name="imageId">Picture identifier</param>
        /// <param name="Width">Width</param>
        /// <param name="Height">Height</param>
        /// <param name="showDefaultPicture">A value indicating whether the default picture is shown</param>
        /// <returns></returns>
        public static string GetPictureUrl(int imageId, int Width, int Height, bool showDefaultPicture)
        {
            Picture picture = GetByPictureID(imageId);
            return GetPictureUrl(picture, Width, Height, showDefaultPicture);
        }

        /// <summary>
        /// Get a picture URL
        /// </summary>
        /// <param name="picture">Picture instance</param>
        /// <param name="Width">Width</param>
        /// <param name="Height">Height</param>
        /// <param name="showDefaultPicture">A value indicating whether the default picture is shown</param>
        /// <returns></returns>
        public static string GetPictureUrl(Picture picture, int Width, int Height, bool showDefaultPicture)
        {
            string url = string.Empty;
            if (picture == null)
            {
                if (showDefaultPicture)
                    url = NoImageURL;
                return url;
            }

            string[] parts = picture.Extension.Split('/');
            string lastPart = parts[parts.Length - 1];
            switch (lastPart)
            {
                case "pjpeg":
                    lastPart = "jpg";
                    break;
                case "x-png":
                    lastPart = "png";
                    break;
                case "x-icon":
                    lastPart = "ico";
                    break;
            }

            string localFilename = string.Empty;

            if (picture.IsNew)
            {
                string filter = string.Format("{0}*.*", picture.PictureID.ToString("0000000"));
                string[] currentFiles = Directory.GetFiles(PictureManager.LocalThumbImagePath, filter);
                foreach (string currentFileName in currentFiles)
                    File.Delete(Path.Combine(PictureManager.LocalThumbImagePath, currentFileName));

                picture = PictureManager.UpdatePicture(picture.PictureID, picture.PictureBinary, picture.Extension, false);
            }

            if ((Width == 0) || (Height == 0))
            {
                localFilename = string.Format("{0}.{1}", picture.PictureID.ToString("0000000"), lastPart);
                if (!File.Exists(Path.Combine(PictureManager.LocalThumbImagePath, localFilename)))
                    File.WriteAllBytes(Path.Combine(PictureManager.LocalThumbImagePath, localFilename), picture.PictureBinary);
            }
            else
            {
                localFilename = string.Format("{0}_{1}_{2}.{3}", picture.PictureID.ToString("0000000"), Width, Height, lastPart);
                if (!File.Exists(Path.Combine(PictureManager.LocalThumbImagePath, localFilename)))
                    using (MemoryStream stream = new MemoryStream(picture.PictureBinary))
                    {
                        Bitmap b = new Bitmap(stream);
                        int newWidth = Width;
                        int newHeight = Height;
                        if (newWidth < 1)
                            newWidth = 1;
                        if (newHeight < 1)
                            newHeight = 1;
                        Bitmap newBitMap = new Bitmap(newWidth, newHeight);
                        Graphics g = Graphics.FromImage(newBitMap);
                        g.DrawImage(b, 0, 0, newWidth, newHeight);
                        newBitMap.Save(Path.Combine(PictureManager.LocalThumbImagePath, localFilename), ImageFormat.Jpeg);
                        newBitMap.Dispose();
                        b.Dispose();
                    }
            }
            url = CommonHelper.GetStoreHTTPLocation(false) + "images/thumbs/" + localFilename;
            return url;
        }

        /// <summary>
        /// Gets a picture
        /// </summary>
        /// <param name="PictureID">Picture identifier</param>
        /// <returns>Picture</returns>
        public static Picture GetByPictureID(int PictureID)
        {
            return PictureDBManager.GetByPictureID(PictureID);
        }

        /// <summary>
        /// Deletes a picture
        /// </summary>
        /// <param name="PictureID">Picture identifier</param>
        public static void DeletePicture(int PictureID)
        {
            string filter = string.Format("{0}*.*", PictureID.ToString("0000000"));
            string[] currentFiles = Directory.GetFiles(PictureManager.LocalThumbImagePath, filter);
            foreach (string currentFileName in currentFiles)
                File.Delete(Path.Combine(PictureManager.LocalThumbImagePath, currentFileName));

            PictureDBManager.DeletePicture(PictureID);
        }

        /// <summary>
        /// If the picture is not valid the an exception is thrown
        /// </summary>
        /// <param name="PictureBinary">Picture binary</param>
        private static void IsValidPicture(byte[] PictureBinary)
        {
            using (MemoryStream stream = new MemoryStream(PictureBinary))
            {
                Bitmap b = new Bitmap(stream);
                int newWidth = 1;
                int newHeight = 1;
                Bitmap newBitMap = new Bitmap(newWidth, newHeight);
                Graphics g = Graphics.FromImage(newBitMap);
                g.DrawImage(b, 0, 0, newWidth, newHeight);
                newBitMap.Dispose();
                b.Dispose();
            }
        }

        /// <summary>
        /// Inserts a picture
        /// </summary>
        /// <param name="PictureBinary">The picture binary</param>
        /// <param name="Extension">The picture extension</param>
        /// <param name="IsNew">A value indicating whether the picture is new</param>
        /// <returns>Picture</returns>
        public static Picture InsertPicture(byte[] PictureBinary, string Extension, bool IsNew)
        {
            IsValidPicture(PictureBinary);
            return PictureDBManager.InsertPicture(PictureBinary, Extension, IsNew);
        }

        /// <summary>
        /// Updates the picture
        /// </summary>
        /// <param name="PictureID">The picture identifier</param>
        /// <param name="PictureBinary">The picture binary</param>
        /// <param name="Extension">The picture extension</param>
        /// <param name="IsNew">A value indicating whether the picture is new</param>
        /// <returns>Picture</returns>
        public static Picture UpdatePicture(int PictureID, byte[] PictureBinary, string Extension, bool IsNew)
        {
            IsValidPicture(PictureBinary);
            return PictureDBManager.UpdatePicture(PictureID, PictureBinary, Extension, IsNew);
        }
        
        /// <summary>
        /// Gets the picture binary array
        /// </summary>
        /// <param name="fs">File stream</param>
        /// <param name="size">Picture size</param>
        /// <returns>Picture binary array</returns>
        public static byte[] GetPictureBits(Stream fs, int size)
        {
            byte[] img = new byte[size];
            fs.Read(img, 0, size);
            return img;
        }
        #endregion

        #region Properties
        /// <summary>
        /// Gets a local thumb image path
        /// </summary>
        public static string LocalThumbImagePath
        {
            get
            {
                string path = HttpContext.Current.Request.PhysicalApplicationPath + "images\\thumbs";
                return path;
            }
        }

        /// <summary>
        /// Gets "noimage" URL
        /// </summary>
        public static string NoImageURL
        {
            get
            {
                string url = CommonHelper.GetStoreHTTPLocation(false) + "images/noDefaultImage.gif";
                return url;
            }
        }
        #endregion
    }
}
